<!DOCTYPE html>
<html>

	<head>
		<meta charset="UTF-8">
		<title>promise</title>
	</head>

	<body>
		<script>
			{
				/*const ajax = function(callback){
					console.log("start");
					setTimeout(()=>{
						callback&&callback.call();
					},1000)
				}
				ajax(function(){
					console.log("Hello World");
				})*/
			} {
				/*const ajax = function(){
					console.log("start");
					return new Promise(function(resolve,reject){
						setTimeout(()=>{
							resolve("hello");
						},1000)
					})
				}
				ajax().then((value)=>{
					console.log(value,"world");
				})*/
			} {
				/*const ajax = function(){
					console.log("start");
					return new Promise(function(resolve,reject){
						setTimeout(function(){
							resolve()
						},1000);
					})
				}
				ajax().then(function(){
					return new Promise(function(resolve,reject){
						setTimeout(function(){
							resolve()
						},2000);
					})
				}).then(()=>{
					console.log("Hello World");
				})*/
			} {
				/*const ajax = function(num){
					console.log("start");
					return new Promise(function(resolve,reject){
						if(num>5){
							resolve();
						}else{
							throw new Errow("出错了");
						}
					})
				}
				ajax(3).then(()=>{
					console.log("Hello World");
				}).catch((err)=>{
					console.log(err);
				})*/
			} {
				// 所有图片加载完再添加到页面
				/*function loadImg(src) {
					return new Promise((resolve, reject) => {
						let img = document.createElement('img');
						img.src = src;
						img.onload = function() {
							resolve(img);
						}
						img.onerror = function(err) {
							reject(err);
						}
					})
				}
				function showImgs(imgs) {
					imgs.forEach(function(img) {
						document.body.appendChild(img);
					})
				}
				Promise.all([
					loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449634314&di=56a92121182ba40c4a640c053dc0c64b&imgtype=0&src=http%3A%2F%2Fb.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%2F9825bc315c6034a8ef5250cec5134954082376c9.jpg'),
					loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449650753&di=5642d7deef9e1e63b6f3868c75b625f0&imgtype=0&src=http%3A%2F%2Fg.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%2Fc2cec3fdfc03924590b2a9b58d94a4c27d1e2500.jpg'),
					loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449650745&di=6d65c12f144a14bb2593901da1e995a1&imgtype=0&src=http%3A%2F%2Fh.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%2F0b46f21fbe096b63491b16ea06338744ebf8ac0e.jpg')
				]).then(showImgs)*/
			}

			{

				// 有一个图片加载完就添加到页面
				/*function loadImg(src){
				    return new Promise((resolve,reject)=>{
				      let img=document.createElement('img');
				      img.src=src;
				      img.onload=function(){
				        resolve(img);
				      }
				      img.onerror=function(err){
				        reject(err);
				      }
				    })
				  }
				
				  function showImgs(img){
				    let p=document.createElement('p');
				    p.appendChild(img);
				    document.body.appendChild(p)
				  }
				
				  Promise.race([
				    loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449634314&di=56a92121182ba40c4a640c053dc0c64b&imgtype=0&src=http%3A%2F%2Fb.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%2F9825bc315c6034a8ef5250cec5134954082376c9.jpg'),
					loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449650753&di=5642d7deef9e1e63b6f3868c75b625f0&imgtype=0&src=http%3A%2F%2Fg.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%2Fc2cec3fdfc03924590b2a9b58d94a4c27d1e2500.jpg'),
					loadImg('https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1559449650745&di=6d65c12f144a14bb2593901da1e995a1&imgtype=0&src=http%3A%2F%2Fh.hiphotos.baidu.com%2Fimage%2Fpic%2Fitem%210b46f21fbe096b63491b16ea06338744ebf8ac0e.jpg')
				  ]).then(showImgs)
				
				*/
			} {
				/*new Promise(resolve=>{
					console.log("start1");
					setTimeout(()=>{
						resolve(100);
					},1000);
				})
				.then(value=>{
					return new Promise(resolve=>{
						console.log("start2");
						console.log(value);
						setTimeout(()=>{
							resolve(200);
						},1000);
					})
				})
				.then(value=>{
					return new Promise(resolve=>{
						console.log("start3");
						console.log(value);
						setTimeout(()=>{
							resolve(300);
						},1000);
					})
				})
				.then(value=>{
					return new Promise(resolve=>{
						console.log("start4");
						console.log(value);
						setTimeout(()=>{
							resolve(400);
						},1000);
					})
				})*/
			} {
				// 构建队列
				/*function queue(things) {
					let promise = Promise.resolve();
					things.forEach(element => {
						promise = promise.then(() => {
							return new Promise(resolve => {
								setTimeout(() => {
									console.log(element)
									resolve('ok');
								}, 1000);
							});
						})
					});
				}
				queue(['a', 'b', 'c']);*/
			} {
				/*async function queue(arr) {
				  let res = null
				  for (let promise of arr) {
				    res = await promise(res)
				  }
				  return await res
				}
				queue(["a", "b", "c"])
				  .then(data => {
				    console.log(data)// abc
				  })*/
				//Promise.reduce也可以用来顺序执行函数，但是可使用的场景非常有限，一般用来读取文件信息，
			}{
				const PENDING = "pending";
				const RESOLVED = "resolved";
				const REJECTED = "rejected";
				function MyPromise(fn){
					let that = this;
					that.state = PENDING;
					that.value = null;
					that.resolvedCallbacks = [];
					that.rejectedCallbacks = [];
					function resolve(value){
						if(that.state === PENDING){
							that.state = RESOLVED;
							that.value = value;
							that.resolvedCallbacks.map(callback=>callback(that.value))
						}
					}
					function reject(value){
						if(that.state === PENDING){
							that.state = REJECTED;
							that.value = value;
							that.rejectedCallbacks.map(callback=>callback(that.value))
						}
					}
					try{
						fn(resolve,reject)
					}catch(e){
						reject(e)
					}
				}
				
				
				MyPromise.prototype.then = function(onFulfilled,onRejected){
					let that = this;
					onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : v => v;
					onRejected = typeof onRejected === 'function' ? onRejected : r=>{throw r};
					if(that.state === PENDING){
						that.resolvedCallbacks.push(onFulfilled)
    					that.rejectedCallbacks.push(onRejected)
					}
					if(that.state === RESOLVED){
						onFulfilled(that.value);
					}
					if(that.state === REJECTED){
						onRejected(that.value);
					}
				}
				
				const ajax = function(){
					console.log("start");
					return new MyPromise(function(resolve,reject){
						setTimeout(()=>{
							resolve("hello");
						},1000)
					})
				}
				ajax().then((value)=>{
					console.log(value,"world");
				})
			}
		</script>
	</body>

</html>